import { LoginPassword, $LoginPassword, UserId } from './model';
import { mainDB } from '../../infra/mysql';
import { RowDataPacket } from 'mysql2';

export interface LoginPasswordRepository {
  /**
   * 根据用户 ID 查询登录密码
   *
   * @param userId 用户 ID
   */
  selectByUserId(userId: UserId): Promise<$LoginPassword>;

  /**
   * 持久化登录密码
   *
   * @param loginPassword 被保存的登录密码
   */
  persist(loginPassword: LoginPassword): Promise<void>;
}

class LoginPasswordMySQLRepository implements LoginPasswordRepository {
  async selectByUserId(userId: number): Promise<$LoginPassword> {
    const sql = `
      select user_id as userId, encrypted_password as encryptedPassword
      from login_password
      where user_id = ?
    `;
    const $password = await mainDB.queryOne(sql, [userId]);
    return !$password ? undefined : this.toLoginPassword($password);
  }

  private toLoginPassword(row: RowDataPacket): LoginPassword {
    return {
      userId: row['userId'],
      encryptedPassword: row['encryptedPassword'],
    };
  }

  async persist(lp: LoginPassword): Promise<void> {
    const sql = `
      insert into login_password set encrypted_password = ?, user_id = ?
      on duplicate key update encrypted_password = ?
    `;
    await mainDB.execute(sql, [lp.encryptedPassword, lp.userId, lp.encryptedPassword]);
  }
}

export const createLoginPasswordRepository = (): LoginPasswordRepository => new LoginPasswordMySQLRepository();
